package com.sisgesbyte.web.managedBean.mantenimiento.administracion;

import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;

import javax.annotation.PostConstruct;
import javax.ejb.EJB;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.ManagedProperty;
import javax.faces.bean.ViewScoped;
import javax.faces.context.FacesContext;
import javax.inject.Inject;
import javax.servlet.http.HttpSession;

import org.primefaces.event.FileUploadEvent;
import org.primefaces.event.SelectEvent;
import org.primefaces.event.UnselectEvent;

import com.sisgesbyte.common.ConstantesInternasSistema;
import com.sisgesbyte.common.Validaciones;
import com.sisgesbyte.dao.beanDao.FiltrosBean;
import com.sisgesbyte.dao.beanDao.FiltrosSQLBean;
import com.sisgesbyte.services.administracion.MantenimientoCategoriaProd;
import com.sisgesbyte.services.administracion.bean.CategoriaProdBean;
import com.sisgesbyte.services.administracion.bean.CategoriaProdListaResponse;
import com.sisgesbyte.services.commonBean.GenericResponse;
import com.sisgesbyte.web.managedBean.common.MantenimientoAbstract;
import com.sisgesbyte.web.managedBean.seguridad.OpcionesControlador;

@ManagedBean
@ViewScoped
public class CategoriaProdMBean extends MantenimientoAbstract implements Serializable{

	private static final long serialVersionUID = 1L;

	@EJB
	private MantenimientoCategoriaProd mantenimientoCategoriaProd;
	@Inject
	private Validaciones validaciones;
	@ManagedProperty(value = "#{opcionesControlador}")
	private OpcionesControlador opcionesControlador;
	private FiltrosSQLBean cadenaFiltros;
	private List<CategoriaProdBean> listaCategoria;
	private List<CategoriaProdBean> hijosPorCategoria;
	private List<CategoriaProdBean> selectedCategoria;
	private List<CategoriaProdBean> listaComboCategoriaProd;
	private String tipoMantenimiento;
	private String saved;
	private String txtBuscar;
	
	
	@PostConstruct
	private void init(){
		saved="";
		tipoMantenimiento = "";
		txtBuscar="";
		crearFiltro();
		llenarComboMenu();
		inicializar();
	}
	
	public OpcionesControlador getOpcionesControlador() {
		return opcionesControlador;
	}

	public void setOpcionesControlador(OpcionesControlador opcionesControlador) {
		this.opcionesControlador = opcionesControlador;
	}

	public String getTipoMantenimiento() {
		return tipoMantenimiento;
	}

	public void setTipoMantenimiento(String tipoMantenimiento) {
		this.tipoMantenimiento = tipoMantenimiento;
	}

	public String getSaved() {
		return saved;
	}

	public void setSaved(String saved) {
		this.saved = saved;
	}

	public String getTxtBuscar() {
		return txtBuscar;
	}

	public void setTxtBuscar(String txtBuscar) {
		this.txtBuscar = txtBuscar;
	}
	
	public List<CategoriaProdBean> getListaCategoria() {
		return listaCategoria;
	}

	public void setListaCategoria(List<CategoriaProdBean> listaCategoria) {
		this.listaCategoria = listaCategoria;
	}

	public List<CategoriaProdBean> getSelectedCategoria() {
		return selectedCategoria;
	}

	public void setSelectedCategoria(List<CategoriaProdBean> selectedCategoria) {
		this.selectedCategoria = selectedCategoria;
	}
	
	public FiltrosSQLBean getCadenaFiltros() {
		return cadenaFiltros;
	}

	public void setCadenaFiltros(FiltrosSQLBean cadenaFiltros) {
		this.cadenaFiltros = cadenaFiltros;
	}

	public List<CategoriaProdBean> getListaComboCategoriaProd() {
		return listaComboCategoriaProd;
	}

	public void setListaComboCategoriaProd(
			List<CategoriaProdBean> listaComboCategoriaProd) {
		this.listaComboCategoriaProd = listaComboCategoriaProd;
	}

	public List<CategoriaProdBean> getHijosPorCategoria() {
		return hijosPorCategoria;
	}

	public void setHijosPorCategoria(List<CategoriaProdBean> hijosPorCategoria) {
		this.hijosPorCategoria = hijosPorCategoria;
	}

	@Override
	public void inicializar() {
		try {
			CategoriaProdListaResponse response =  mantenimientoCategoriaProd.listaCategoriasProducto(ObtenerIdTransaccion(), cadenaFiltros);
			if (Integer.valueOf(response.getCodigoRespuesta()) > -1) {
				
				if(getTxtBuscar().contains("++")){
					//cargamos la lista de resultados temporalmente
					hijosPorCategoria = response.getListaCategoriaProductos();
					//iniciamos o limpiamos los datos anteriores con una nueva instancia de listacategoria
					listaCategoria = new ArrayList<CategoriaProdBean>();
					//empezamos a buscar los hijos del codigo ingresado en el buscador
					mostrarHijos(Integer.valueOf(getTxtBuscar().replace("++", "")));
				}else{
					//cargamos lista 
					listaCategoria = response.getListaCategoriaProductos();
				}
				
			} else {
				System.out.println("No se encontro Data "+ response.getMensajeRespuesta());
			}
		} catch (Exception e) {
			System.out.println("Ocurrio un error al cargar Lista " + e);
		}
	}
	
	//metodo para obtener la estructura de hijos de una categoria
	public void mostrarHijos(int padreId) {
		for (CategoriaProdBean ls : hijosPorCategoria) {
			if (padreId == ls.getPadre_id()) {
				listaCategoria.add(ls);
				mostrarHijos(ls.getId());
			}
		}
	}
	@Override
	public void unSelect(UnselectEvent event) {
		opcionesControlador.habilitarControles(selectedCategoria.size());
	}

	@Override
	public void checkSelect(SelectEvent event) {
		opcionesControlador.habilitarControles(selectedCategoria.size());
	}

	@Override
	public void seleccionarItem(SelectEvent event) {
		opcionesControlador.habilitarControles(selectedCategoria.size());
	}

	@Override
	public void dobleSelect(SelectEvent event) {
		List<CategoriaProdBean> selected = new ArrayList<CategoriaProdBean>();
		selected.add((CategoriaProdBean) event.getObject());
		setSelectedCategoria(selected);
		setSaved("");
		opcionesControlador.habilitarControles(selectedCategoria.size());
		setTipoMantenimiento(ConstantesInternasSistema.TIPO_MANTENIMIENTO_UPDATE);
	}

	@Override
	public void nuevoItem() {
		setSaved("");
		limpiarFormulario();
		setTipoMantenimiento(ConstantesInternasSistema.TIPO_MANTENIMIENTO_NUEVO);
	}

	@Override
	public void editItem() {
		setSaved("");
		setTipoMantenimiento(ConstantesInternasSistema.TIPO_MANTENIMIENTO_UPDATE);
	}

	@Override
	public void updateInsertItem() {
		if(tipoMantenimiento.equalsIgnoreCase(ConstantesInternasSistema.TIPO_MANTENIMIENTO_NUEVO)){
			guardarItem();
		}
		if(tipoMantenimiento.equalsIgnoreCase(ConstantesInternasSistema.TIPO_MANTENIMIENTO_UPDATE)){
			modificarItem();
		}
	}

	@Override
	public String ObtenerIdTransaccion() {
		FacesContext fCtx = FacesContext.getCurrentInstance();
		HttpSession session = (HttpSession) fCtx.getExternalContext().getSession(false);
		String sessionId = session.getId().replace(".undefined", "");
		return sessionId;
	}

	@Override
	public void guardarItem() {
		GenericResponse response = null;
		try{
			for( CategoriaProdBean bean: listaSeleccionados(selectedCategoria)){
				response = mantenimientoCategoriaProd.nuevaCategoriaProd(ObtenerIdTransaccion(), bean);
				if(response.getCodigoRespuesta().equals(ConstantesInternasSistema.CODIGO_EXITO)){
					setSaved(ConstantesInternasSistema.SAVED_ITEM_OK);
					System.out.println("Se registro Correctamente");
				}else{
					setSaved(ConstantesInternasSistema.SAVED_ITEM_ERROR);
					System.out.println("Hubo un error al Registrar " + response.getCodigoRespuesta() + " - "+ response.getMensajeRespuesta());
				}
			}
			limpiarFormulario();
			inicializar();
		}catch(Exception e){
			setSaved(ConstantesInternasSistema.SAVED_ITEM_ERROR);
			System.out.println("Error en el proceso " + e);
		}
	}

	@Override
	public void modificarItem() {
		GenericResponse response = null;
		try{
			for( CategoriaProdBean bean: listaSeleccionados(selectedCategoria)){
				response = mantenimientoCategoriaProd.editCategoriaProd(ObtenerIdTransaccion(), bean);
				if(response.getCodigoRespuesta().equals(ConstantesInternasSistema.CODIGO_EXITO)){
					setSaved(ConstantesInternasSistema.SAVED_ITEM_OK);
					System.out.println("Se Acualizo correctamente");
				}else{
					setSaved(ConstantesInternasSistema.SAVED_ITEM_ERROR);
					System.out.println("Hubo un Error al Actualizar de BD " + response.getCodigoRespuesta() +" - " +response.getMensajeRespuesta() );
				}
			}
			inicializar();
		}catch(Exception e){
			System.out.println("Error en el proceso " + e);
		}
	}

	@Override
	public void eliminarItem() {
		GenericResponse response = null;
		try{
			for(CategoriaProdBean bean :selectedCategoria){					
				response = mantenimientoCategoriaProd.deletecategoriaProd(ObtenerIdTransaccion(), bean.getId());
				if(response.getCodigoRespuesta().equals(ConstantesInternasSistema.CODIGO_EXITO)){
					System.out.println("Se elimino Correctamente");
				}else{
					System.out.println("No se pudo Eliminar de BD " + response.getCodigoRespuesta() +" - " + response.getMensajeRespuesta());
				}
			}
			inicializar();
			opcionesControlador.desactivarControles();
		}catch(Exception e){
			System.out.println("Hubo un error al tratar de Eliminar " + e);
		}
	}

	@Override
	public void actualizarEstado() {
		GenericResponse response = null;
		try{
			for(CategoriaProdBean bean :listaSeleccionados(listaCategoria)){
				response = mantenimientoCategoriaProd.editCategoriaProd(ObtenerIdTransaccion(), bean);
				if(response.getCodigoRespuesta().equals(ConstantesInternasSistema.CODIGO_EXITO)){
					System.out.println("Se Acualizo correctamente");
				}else{
					System.out.println("No se pudo actualizar el Item con codigo " + bean.getId());
				}
			}
			inicializar();
		}catch(Exception e){
			System.out.println("Hubo un error al actualizar el estado");
		}	
	}

	@Override
	public void limpiarFormulario() {
		List<CategoriaProdBean> listaBean = new ArrayList<CategoriaProdBean>();
		CategoriaProdBean  bean = new CategoriaProdBean();
		bean.setNombre("");
		bean.setNivel(1);
		listaBean.add(bean);
		setSelectedCategoria(listaBean);
	}
	//metodo para cargar los elementos del combo
	public void llenarComboMenu(){
		try{
			setListaComboCategoriaProd(mantenimientoCategoriaProd.listaCategoriasProducto(ObtenerIdTransaccion(), cadenaFiltros).getListaCategoriaProductos());
		}catch(Exception e){
			System.out.println("Error al cargar Combo ");
		}
		
	}
	/*Metodo para recorrer y validar los tipos de campos seleccionados
	 */
	public List<CategoriaProdBean> listaSeleccionados(List<CategoriaProdBean> listaRequest){
		List<CategoriaProdBean> response = new ArrayList<CategoriaProdBean>();
		for(CategoriaProdBean listaBean : listaRequest){
			CategoriaProdBean bean = new CategoriaProdBean();
			bean.setDescripcion(validaciones.validarCamposString(listaBean.getDescripcion()));
			bean.setEstado(listaBean.getEstado());
			bean.setId(listaBean.getId());
			bean.setImagen(validaciones.validarCamposString(listaBean.getImagen()));
			bean.setNivel(listaBean.getNivel());
			bean.setNombre(validaciones.validarCamposString(listaBean.getNombre()));
			bean.setPadre_id(listaBean.getPadre_id());
			response.add(bean);
		}
		return response;
	}
	
	public void actualizarNivel(){
		for(CategoriaProdBean listaBean : selectedCategoria){
			for(CategoriaProdBean row : listaComboCategoriaProd){
				if(row.getId()== listaBean.getPadre_id()){
					selectedCategoria.get(0).setNivel(row.getNivel() + 1);
				}
			}
		}
	}
	
	@Override
	public void crearFiltro() {
		FiltrosSQLBean filtroSQL = new FiltrosSQLBean();
		try{
			if(getTxtBuscar() !=null && !getTxtBuscar().contains("++") && getTxtBuscar().toString().length() > 0){

				List<Object> valores = new ArrayList<>();
				List<FiltrosBean> filtro = new ArrayList<FiltrosBean>();
				FiltrosBean listaCampo = new FiltrosBean();
				List<String> campo = new ArrayList<String>();
				campo.add("cp.id");
				campo.add("cp.nombre");
				campo.add("cp.descripcion");
				campo.add("cp.nombre_padre");
				campo.add("cp.nivel");
				listaCampo.setCampos(campo);
				listaCampo.setOperador("like");
				filtro.add(listaCampo);
				filtroSQL.setListaFiltros(filtro);
				//++ significa que va a buscar los hijos del codigo ingresado en el bucador
				if(getTxtBuscar().contains("++")){
					setTxtBuscar(getTxtBuscar().replace("++", ""));
				}
				valores.add("%"+getTxtBuscar() + "%");
				filtroSQL.setListaValores(valores);
				
			}else{
				filtroSQL.setCampoOrden("cp.id");
				filtroSQL.setTipoOrden("desc");
			}
			setCadenaFiltros(filtroSQL);
			inicializar();
			opcionesControlador.habilitarControles(0);
		}catch(Exception e){
			System.out.println("Error al crear filtro " + e);
			filtroSQL.setCampoOrden("cp.id");
			filtroSQL.setTipoOrden("desc");
		}
	}
	
	public void handleFileUpload(FileUploadEvent event){
         System.out.println("fileUploadListener invoked. " + event.getFile().getFileName());
	}
}
